package com.fowo.api.om.service.impl;

import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import com.fowo.api.common.model.RException;
import com.fowo.api.common.util.ContextHolder;
import com.fowo.api.om.model.OmFileMigratePo;
import com.fowo.api.om.model.OmFileMigrateResult;
import com.fowo.api.om.service.OmFileService;
import com.fowo.api.sys.entity.SysFile;
import com.fowo.api.sys.mapper.SysFileMapper;
import com.fowo.api.sys.service.FileStorageService;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.BeansException;
import org.springframework.stereotype.Service;

import javax.annotation.Resource;
import java.io.InputStream;
import java.util.List;

/**
 * 运维文件服务实现
 * @author yl_ls
 */
@Slf4j
@Service
public class OmFileServiceImpl implements OmFileService {

    @Resource
    private SysFileMapper sysFileMapper;

    @Override
    public OmFileMigrateResult migrate(OmFileMigratePo migratePo) {
        int handles = 0;
        int errors = 0;

        log.info("启动运维文件迁移");


        FileStorageService sourceStorageService;
        try {
            sourceStorageService = ContextHolder.getApplicationContext().getBean(migratePo.getSourceStorageType(), FileStorageService.class);
        } catch (BeansException e1) {
            throw new RException(String.format("未能获取命名为“%s”的源存储服务！", migratePo.getSourceStorageType()));
        }
        FileStorageService targetStorageService;
        try {
            targetStorageService = ContextHolder.getApplicationContext().getBean(migratePo.getTargetStorageType(), FileStorageService.class);
        } catch (BeansException e1) {
            throw new RException(String.format("未能获取命名为“%s”的目标存储服务！", migratePo.getSourceStorageType()));
        }

        List<SysFile> files = sysFileMapper.selectList(Wrappers.<SysFile>query()
                .eq("storage_type", migratePo.getSourceStorageType())
                .select("id", "storage_key")
        );

        log.info("运维文件迁移 - 需要处理 {} 个文件", files.size());
        for (SysFile file : files) {
            try {
                try(InputStream inputStream = sourceStorageService.read(file.getStorageKey())) {
                    targetStorageService.write(file.getStorageKey(), true, inputStream);
                }
                file.setStorageType(migratePo.getTargetStorageType());
                sysFileMapper.updateById(file);
                handles++;
                if (Boolean.TRUE.equals(migratePo.getDeleteSource())) {
                    try {
                        sourceStorageService.delete(file.getStorageKey());
                    } catch (Exception i) {
                        // 忽略删除源失败问题
                    }
                }
            } catch (Exception e) {
                log.error("运维文件迁移 - 迁移 {} 失败: {}", file.getStorageKey(), e.getLocalizedMessage());
            }
        }

        log.info("运维文件迁移完成，成功处理 {} 个，失败 {} 个", handles, errors);

        OmFileMigrateResult result = new OmFileMigrateResult();
        result.setHandles(handles);
        result.setErrors(errors);
        return result;
    }
}
